ラズパイにカメラモジュールにセットしてPythonで写真や動画を撮る
最近IoTカメラに興味があり、ラズパイでもカメラを扱ってみたいと思っていました。そこで見つけたのがFreenove FNK0056です。
ラズパイ公式のカメラモジュールがあることは知っていたのですが、お値段が3倍ぐらい違います。お値打ち価格に心を惹かれ「やってみる」の精神で試してみることにしました。
なおマニュアルがGitHubで公開されているので、気になった人は覗いてみるといいと思います。
セットアップ
ラズパイ
Raspberry Pi 3 Model Bを使いました。OSは「Raspberry Pi OS Full (64-bit)」です。
OSの詳細はこちら。
$ lsb_release -a No LSB modules are available. Distributor ID: Debian Description: Debian GNU/Linux 11 (bullseye) Release: 11 Codename: bullseye
また、VNCでMac Book Proから接続しています。
Freenove FNK0056
YouTubeにセットアップ動画が上がってるのでこれに従って準備します。特に困った点はありませんでした。
我が家では以下のような形になりました。ちなみにケースはこちらのものです。
やってみる
GitHubに上がっているチュートリアルに従って触っていきます。チュートリアルにはラズパイ用とJetson Nano用があるので間違わないようにします。
ターミナルからカメラを動かす
Hello World的なコマンドであるlibcamera-hello
を試します。
libcamera-helloは、カメラ用の「hello world」アプリケーションに相当するものです。カメラを起動し、プレビュー・ウィンドウを表示し、それ以外は何もしません。例えば
libcamera-hello
は、約5秒間プレビューウィンドウが表示されるはずです。ラズパイ公式ドキュメントを翻訳して引用
ただし、1つ注意点があります。
libcamera-apps は、Pi 0 から 3 のデバイスで最新の Bullseye イメージを実行すると、正しく動作しません。 回避策としては、ターミナルを開き、"sudo raspi-config "を実行し、"Advanced Options "に移動し、以下を有効にします。"Glamor "グラフィックアクセラレーションを使用します。その後、Piを再起動します。
チュートリアルを翻訳して引用
今回使っているラズパイのモデルが3B、OSもBullseyeということで回避策を行いました。チュートリアルには図も含まれているので特に迷うこともありませんでした。
ターミナルから以下のコマンドを実行してみます。
libcamera-hello
数秒間プレビューウィンドウが表示されました。
Pythonで写真撮影
ここからはRaspberry Pi OSにデフォルトで入っているPython IDEであるThonnyでコードを書いていきます。また、カメラを制御するのにはPiCamera2というライブラリを使います。
以下のコードを実行します。
from picamera2 import Picamera2, Preview import time picam2 = Picamera2() camera_config = picam2.create_preview_configuration() picam2.configure(camera_config) picam2.start_preview(Preview.QTGL) picam2.start() time.sleep(2) picam2.capture_file("test.jpg") picam2.close()
実行してみます。プレビューウィンドウが表示され、2秒後にキャプチャが撮られます。
プレビューの設定を変更することもできます。より変化がわかりやすいようにチュートリアルのコードに少し手を加えて、画像を回転してみます。
from picamera2 import Picamera2, Preview from libcamera import Transform picam2 = Picamera2() picam2.start_preview(Preview.QTGL, x=100, y=200, width=800, height=600, transform=Transform(hflip=1, vflip=1)) picam2.start()
Pythonで動画撮影
次は動画です。H.264形式で撮影します。
Picamera2では、ビデオのキャプチャとエンコードのプロセスはほぼ自動化されています。アプリケーションは、画像データの圧縮に使用するエンコーダと、圧縮されたデータストリームの出力方法を定義するだけです。
チュートリアルを翻訳して引用
from picamera2.encoders import H264Encoder from picamera2 import Picamera2 import time picam2 = Picamera2() video_config = picam2.create_video_configuration() picam2.configure(video_config) encoder = H264Encoder(bitrate=10000000) output = "test.h264" picam2.start_recording(encoder, output) time.sleep(10) picam2.stop_recording()
このような動画が撮れました。
次は1つのスクリプトの中でビットレートを3段階で変えながら動画を撮ってみます。
import time from picamera2.encoders import H264Encoder, Quality from picamera2 import Picamera2 picam2 = Picamera2() video_config = picam2.create_video_configuration() picam2.configure(video_config) low_encoder = H264Encoder(bitrate=1000000) picam2.start_recording(low_encoder, 'low.h264') time.sleep(5) picam2.stop_recording() medium_encoder = H264Encoder(bitrate=5000000) picam2.start_recording(medium_encoder, 'medium.h264') time.sleep(5) picam2.stop_recording() high_encoder = H264Encoder(bitrate=10000000) picam2.start_recording(high_encoder, 'high.h264') time.sleep(5) picam2.stop_recording()
マニュアルではpicam2.start_recordingの"quality"という引数を指定する方式でしたが、撮影した動画に違いが見られず、実装の調査を行ったところ、この引数は機能していないことが分かりました(2023.5.2現在)。本件はPicamera2のIssueとして起票しているので、詳細はこちらをご覧ください。
以下の3つの動画が得られました。特に1つめの低ビットレートでは顕著に画質の違いがあることが分かります。
ファイルサイズにも差が出ていますね。
$ ls -ltr 合計 7436 -rw-r--r-- 1 pi pi 589947 5月 2 17:14 low.h264 -rw-r--r-- 1 pi pi 3066060 5月 2 17:14 medium.h264 -rw-r--r-- 1 pi pi 3950489 5月 2 17:14 high.h264
おわりに
今回はFreenoveのカメラモジュールをラズパイにセットアップしました。
ハードウェア、ということで身構えていたものの、動かすだけであれば思ったよりも簡単でした。特にPythonのコードがあることでどんな処理を行っているのか分かりやすくてよかったです。
一方で、より深く触っていくのであればカメラや写真、動画といったものに対する知識も必要になってくるように思いました。このあたりもキャッチアップしていきたいと思います。